import javax.swing.*;
import java.awt.*;
import java.io.File;
import java.util.ListIterator;

class MainFrame extends JFrame
{
	/**
	 * 
	 */
	private static final long		serialVersionUID	= 1L;
	
	
	private Internationalization	language;
	
	/*
	 * Components declarations
	 */
	private JFileChooser			fileChooser;
	
	// JPanels
	protected JPanel				mainPanel;
	protected JPanel				displayPanel;
	protected JPanel				propertyPanel;
	protected DrawingPanel			drawPanel;
	protected JScrollPane			scroller;
	protected JScrollPane			errorsScroller;
	protected JScrollPane			commentsScroller;
	protected JTextArea				comments;
	protected JTextArea				errors;
	
	// Menus
	protected JMenuBar				menuBar;
	protected JMenu					file;
	protected JMenu					action;
	protected JMenu					options;
	protected JMenu					help;
	
	protected JMenuItem				jmiNew;
	protected JMenuItem				jmiOpen;
	protected JMenuItem				jmiSave;
	protected JMenuItem				jmiSaveAs;
	protected JMenuItem				jmiLoadAnimation;
	protected JMenuItem				jmiSaveAnimation;
	protected JMenuItem				jmiSaveAnimationAs;
	protected JMenuItem				jmiQuit;
	protected JMenuItem				jmiSelectAlgo;
	protected JMenuItem				jmiPrepareAnimation;
	protected JMenuItem				jmiDisplayResult;
	protected JMenuItem				jmiTemporized;
	protected JMenuItem				jmiStepByStep;
	protected JMenuItem				jmiStepForward;
	protected JMenuItem				jmiStepBackWards;
	protected JMenuItem				jmiManual;
	protected JMenuItem				jmiAbout;
	
	// ToolBar
	protected JToolBar				toolbar;
	
	protected JButton				bNew;
	protected JButton				bOpen;
	protected JButton				bSave;
	protected JButton				bLoadAnim;
	protected JButton				bSaveAnim;
	protected JButton				bSelectAlgo;
	protected JButton				bPrepare;
	protected JButton				bDisplay;
	protected JButton				bTemporize;
	protected JButton				bStep;
	protected JButton				bPrevious;
	protected JButton				bNext;
	protected JButton				bStop;
	protected JButton				bRefresh;
	
	private Automaton				a1, a2;
	private Animation 				anim;
	private ListIterator<Automaton> automI;
	private OpenAutomatonListener	openAutomatonListener;
	private CloseWindowListener		closeWindowListener;
	private TemporizedAnimationLisner temporizedAnimationLisner;
	private LoadAnimationListener loadAnimationListener;
	private ForwardAnimationListener forwardAnimationListener;
	private BackwardAnimationListener backwardAnimationListener;
	private RefreshListener refreshListener;
	private DisplayResultListener displayResultListener;
	
	public MainFrame()
	{
		super();
		componnentsInitialisation();
	}
	
	protected void componnentsInitialisation()
	{
		language = new Internationalization("fr", "FR");
		
		openAutomatonListener = new OpenAutomatonListener(this);
		closeWindowListener = new CloseWindowListener(this);
		temporizedAnimationLisner = new TemporizedAnimationLisner(this);
		loadAnimationListener = new LoadAnimationListener(this);
		forwardAnimationListener = new ForwardAnimationListener(this);
		backwardAnimationListener = new BackwardAnimationListener(this);
		refreshListener = new RefreshListener(this);
		displayResultListener = new DisplayResultListener(this);
		
		fileChooser = new JFileChooser();
		setTitle(language.sTitle);
		
		/*
		 * JPanels initialisation
		 */
		mainPanel = new JPanel();
		displayPanel = new JPanel();
		propertyPanel = new JPanel();
		drawPanel = new DrawingPanel();
		
		mainPanel.setLayout(new BorderLayout());
		mainPanel.add(displayPanel, BorderLayout.CENTER);
		mainPanel.add(propertyPanel, BorderLayout.EAST);
		
		scroller = new JScrollPane(drawPanel,
				JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED,
				JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);
		comments = new JTextArea("comentaire");
		errors = new JTextArea("erreurs");
		
		errorsScroller = new JScrollPane(errors,
				JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED,
				JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);
		
		commentsScroller = new JScrollPane(comments,
				JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED,
				JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);
		
		
		
		drawPanel.setPreferredSize(new Dimension(2000,2000));
		propertyPanel.setPreferredSize(new Dimension(200, 1000));
		scroller.setPreferredSize(new Dimension(800, 800));
		errorsScroller.setPreferredSize(new Dimension(800, 200));
		commentsScroller.setPreferredSize(new Dimension(200, 800));
		errors.setPreferredSize(new Dimension(800, 2000));
		comments.setPreferredSize(new Dimension(180, 2000));
		
		displayPanel.setLayout(new BorderLayout());
		displayPanel.add(scroller, BorderLayout.CENTER);
		displayPanel.add(commentsScroller, BorderLayout.WEST);
		displayPanel.add(errorsScroller, BorderLayout.SOUTH);
		
		//propertyPanel.add(new JButton("propriete"));
		
		/*
		 * Menu Bar
		 */
		menuBar = new JMenuBar();
		this.setJMenuBar(menuBar);
		
		/*
		 * File menu
		 */

		file = new JMenu(language.sMenuFile);
		file.setMnemonic(language.sMenuFile.charAt(0));
		

		jmiNew = new JMenuItem(language.sNew);
		jmiNew.setIcon(new ImageIcon( getClass() .getResource( "images/new.png")));
		file.add(jmiNew);
		
		file.add(new JSeparator());
		
		jmiOpen = new JMenuItem(language.sOpen);
		jmiOpen.setIcon(new ImageIcon( getClass() .getResource( "images/open.gif")));
		jmiOpen.addActionListener(openAutomatonListener);
		file.add(jmiOpen);
		
		jmiSave = new JMenuItem(language.sSave);
		jmiSave.setIcon(new ImageIcon( getClass() .getResource( "images/save.png")));
		file.add(jmiSave);
		
		jmiSaveAs = new JMenuItem(language.sSaveAs);
		file.add(jmiSaveAs);
		file.add(new JSeparator());
		
		jmiLoadAnimation = new JMenuItem(language.sLoadAnimation);
		jmiLoadAnimation.setIcon(new ImageIcon( getClass() .getResource( "images/loadAnim.png")));
		file.add(jmiLoadAnimation);
		
		jmiSaveAnimation = new JMenuItem(language.sSaveAnimation);
		jmiSaveAnimation.setIcon(new ImageIcon( getClass() .getResource( "images/saveAnim.png")));
		file.add(jmiSaveAnimation);
		
		jmiSaveAnimationAs = new JMenuItem(language.sSaveAnimationAs);
		file.add(jmiSaveAnimationAs);
		file.add(new JSeparator());
		
		jmiQuit = new JMenuItem(language.sQuit);
		jmiQuit.setIcon(new ImageIcon( getClass() .getResource( "images/quit.png")));
		jmiQuit.addActionListener(closeWindowListener);
		file.add(jmiQuit);
		
		/*
		 * Action menu
		 */
		action = new JMenu(language.sMenuAction);
		action.setMnemonic(language.sMenuAction.charAt(0));
		
		jmiSelectAlgo = new JMenuItem(language.sSelectAlgo);
		jmiSelectAlgo.setIcon(new ImageIcon( getClass() .getResource( "images/algo.png")));
		action.add(jmiSelectAlgo);
		
		jmiPrepareAnimation = new JMenuItem(language.sPrepareAnimation);
		jmiPrepareAnimation.setIcon(new ImageIcon( getClass() .getResource( "images/prepare.png")));
		jmiPrepareAnimation.addActionListener(loadAnimationListener);
		action.add(jmiPrepareAnimation);
		
		action.add(new JSeparator());
		
		jmiDisplayResult = new JMenuItem(language.sDisplayResult);
		jmiDisplayResult.setIcon(new ImageIcon( getClass() .getResource( "images/display.png")));
		jmiDisplayResult.addActionListener(displayResultListener);
		action.add(jmiDisplayResult);
		
		jmiTemporized = new JMenuItem(language.sTemporized);
		jmiTemporized.setIcon(new ImageIcon( getClass() .getResource( "images/temporized.png")));
		jmiTemporized.addActionListener(temporizedAnimationLisner);
		action.add(jmiTemporized);
		
		//jmiStepByStep = new JMenuItem(language.sStepByStep);
		//jmiStepByStep.setIcon(new ImageIcon( getClass() .getResource( "images/step.png")));
		//action.add(jmiStepByStep);
		
		action.add(new JSeparator());
		
		jmiStepForward = new JMenuItem(language.sStepForward);
		jmiStepForward.setIcon(new ImageIcon( getClass() .getResource( "images/next.png")));
		jmiStepForward.addActionListener(forwardAnimationListener);
		action.add(jmiStepForward);
		
		jmiStepBackWards = new JMenuItem(language.sStepBackWards);
		jmiStepBackWards.setIcon(new ImageIcon( getClass() .getResource( "images/previous.png")));
		jmiStepBackWards.addActionListener(backwardAnimationListener);
		action.add(jmiStepBackWards);
		
		/*
		 * Options menu
		 */
		options = new JMenu(language.sMenuOption);
		options.setMnemonic(language.sMenuOption.charAt(0));
		
		/*
		 * Help menu
		 */
		help = new JMenu(language.sMenuHelp);
		help.setMnemonic(language.sMenuHelp.charAt(0));
		
		jmiManual = new JMenuItem(language.sManual);
		jmiManual.setIcon(new ImageIcon( getClass() .getResource( "images/manual.png")));
		help.add(jmiManual);
		
		jmiAbout = new JMenuItem(language.sAbout);
		jmiAbout.setIcon(new ImageIcon( getClass() .getResource( "images/about.png")));
		help.add(jmiAbout);
		
		/*
		 * Adding created menus to menuBar
		 */
		menuBar.add(file);
		menuBar.add(action);
		menuBar.add(options);
		menuBar.add(help);
		
		/* */
		toolbar = new JToolBar();
		
		bNew = new JButton(new ImageIcon( getClass() .getResource( "images/new.png")));
		bNew.setToolTipText(language.sNew);
		toolbar.add(bNew);
		
		bOpen = new JButton(new ImageIcon( getClass() .getResource( "images/open.gif")));
		bOpen.setToolTipText(language.sOpen);
		bOpen.addActionListener(openAutomatonListener);
		toolbar.add(bOpen);
		
		bSave = new JButton(new ImageIcon( getClass() .getResource( "images/save.png")));
		bSave.setToolTipText(language.sSave);
		toolbar.add(bSave);
		
		toolbar.add(new JToolBar.Separator());
		
		bLoadAnim = new JButton(new ImageIcon( getClass() .getResource( "images/loadAnim.png")));
		bLoadAnim.setToolTipText(language.sLoadAnimation);
		toolbar.add(bLoadAnim);
		
		bSaveAnim = new JButton(new ImageIcon( getClass() .getResource( "images/saveAnim.png")));
		bSaveAnim.setToolTipText(language.sSaveAnimation);
		toolbar.add(bSaveAnim);
		
		toolbar.add(new JToolBar.Separator(new Dimension(20, 20)));
		
		bSelectAlgo = new JButton(new ImageIcon( getClass() .getResource( "images/algo.png")));
		bSelectAlgo.setToolTipText(language.sSelectAlgo);
		toolbar.add(bSelectAlgo);
		
		bPrepare = new JButton(new ImageIcon( getClass() .getResource( "images/prepare.png")));
		bPrepare.setToolTipText(language.sPrepareAnimation);
		bPrepare.addActionListener(loadAnimationListener);
		toolbar.add(bPrepare);
		
		toolbar.add(new JToolBar.Separator());
		
		bDisplay = new JButton(new ImageIcon( getClass() .getResource( "images/display.png")));
		bDisplay.setToolTipText(language.sDisplayResult);
		bDisplay.addActionListener(displayResultListener);
		toolbar.add(bDisplay);
		
		bTemporize = new JButton(new ImageIcon( getClass() .getResource( "images/temporized.png")));
		bTemporize.setToolTipText(language.sTemporized);
		bTemporize.addActionListener(temporizedAnimationLisner);
		toolbar.add(bTemporize);
		
		//bStep = new JButton(new ImageIcon( getClass() .getResource( "images/step.png")));
		//bStep.setToolTipText(language.sStepByStep);
		//toolbar.add(bStep);
		
		toolbar.add(new JToolBar.Separator());
		
		bPrevious = new JButton(new ImageIcon( getClass() .getResource( "images/previous.png")));
		bPrevious.setToolTipText(language.sStepBackWards);
		bPrevious.addActionListener(backwardAnimationListener);
		toolbar.add(bPrevious);
		
		bNext = new JButton(new ImageIcon( getClass() .getResource( "images/next.png")));
		bNext.setToolTipText(language.sStepForward);
		bNext.addActionListener(forwardAnimationListener);
		toolbar.add(bNext);
		
		bStop = new JButton(new ImageIcon( getClass() .getResource( "images/stop.png")));
		bStop.setToolTipText(language.sStopAnim);
		toolbar.add(bStop);
		
		toolbar.add(new JToolBar.Separator());
		
		bRefresh = new JButton(new ImageIcon( getClass() .getResource( "images/refresh.png")));
		bRefresh.setToolTipText(language.sRefresh);
		bRefresh.addActionListener(refreshListener);
		toolbar.add(bRefresh);
		
		mainPanel.add(toolbar, BorderLayout.PAGE_START);
		
		this.setContentPane(mainPanel);
		this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		
		
	}
	
	protected void openAutomaton()
	{
		fileChooser.setDialogTitle("");
		int returnVal = fileChooser.showOpenDialog(this);
		if (returnVal == JFileChooser.APPROVE_OPTION)
		{
			File file = fileChooser.getSelectedFile();
			// System.out.println(file);
			a1 = new AutomatonParser(file).parse();
			//System.out.println("\naffichage de l'automate");
			//System.out.println(a1);
			//System.out.println("appel de setAotom");
			drawPanel.setAutom(a1);
			updateErrors(a1.toString());
			//System.out.println("appel de repaint");
			
			drawPanel.repaint();
		}
	}
	
	public void loadAnimation()
	{
		Determinisation d = new Determinisation();
		
		anim = d.calculus(a1);
		automI = anim.getautomata().listIterator();
	}
	
	public void forwardAnim()
	{
		if(automI.hasNext())
		{
			a2 = automI.next();
			drawPanel.setAutom(a2);
			updateErrors(a2.toString());
			drawPanel.repaint();
		}
		
	}
	
	public void backwardAnim()
	{
		if(automI.hasPrevious())
		{
			a2 = automI.previous();
			drawPanel.setAutom(a2);
			updateErrors(a2.toString());
			drawPanel.repaint();
		}
	}
	
	
	public void displayResult()
	{
//		System.out.println("animation begin.");
		Determinisation d = new Determinisation();
		
		anim = d.calculus(a1);
		automI = anim.getautomata().listIterator();
		//System.out.println("animation loaded.");
		
		while (automI.hasNext())
		{
			a2 = automI.next();
		}
		drawPanel.setAutom(a2);
		drawPanel.repaint();
		updateErrors(a2.toString());
	}
	
	
	public void animate()
	{
		//System.out.println("animation begin.");
		Determinisation d = new Determinisation();
		
		anim = d.calculus(a1);
		automI = anim.getautomata().listIterator();
		//System.out.println("animation loaded.");
		
		while (automI.hasNext())
		{
			a2 = automI.next();
			//System.out.println(a2);
			drawPanel.setAutom(a2);
			drawPanel.repaint();
			//System.out.println("animation step.");
			updateErrors(a2.toString());
			/*try
			{
				Thread.sleep(2000);
			}
			catch (InterruptedException e)
			{
				System.out.println("probleme de sleep.");
			}*/
			
		}
	}
	
	public void refresh()
	{
		System.out.println("refreshing");
			drawPanel.repaint();
		
	}
	
	public void updateComments(String text)
	{
		comments.setText(text);
	}
	
	public void updateErrors(String text)
	{
		errors.setText(text);
	}
	
	protected void closeWindow()
	{
		this.dispose();
	}
}
